package com.seanzx.dp.memory;

import com.seanzx.dp.common.MetaTables;
import com.seanzx.dp.entity.Table;
import com.seanzx.dp.ProcessorController;
import com.seanzx.dp.common.ColumnType;
import com.seanzx.dp.entity.Column;

import java.util.*;

public class TableBuffer {
    private static final ProcessorController PROCESSOR_CONTROLLER = ProcessorController.get();

    private static final Map<String, List<Table>> BUFFER = new HashMap<>();

    static {
        init();
    }

    public static void init() {
        List<List<String>> tables = PROCESSOR_CONTROLLER.select("information_schema", "TABLES",
                MetaTables.tables().getColumns(), null).getData();
        for (List<String> tableCols : tables) {
            Table table = Table.builder().tableSchema(tableCols.get(0))
                    .name(tableCols.get(1))
                    .description(null)
                    .columns(new ArrayList<>()).build();
            List<Table> databaseTables = BUFFER.getOrDefault(table.getTableSchema(), new ArrayList<>());
            databaseTables.add(table);
            BUFFER.put(table.getTableSchema(), databaseTables);
        }

        List<List<String>> columns = PROCESSOR_CONTROLLER.select("information_schema", "COLUMNS",
                MetaTables.columns().getColumns(), null).getData();
        for (List<String> columnCols : columns) {
            Column column = Column.builder()
                    .tableSchema(columnCols.get(0)).tableName(columnCols.get(1))
                    .name(columnCols.get(2)).type(ColumnType.from(columnCols.get(3)))
                    .length(Integer.valueOf(columnCols.get(4)))
                    .index(Integer.valueOf(columnCols.get(5)))
                    .build();
            List<Table> databaseTables = BUFFER.get(column.getTableSchema());
            for (Table databaseTable : databaseTables) {
                if (databaseTable.getName().equals(column.getTableName())) {
                    databaseTable.getColumns().add(column);
                    break;
                }
            }
        }
        System.out.println("init buffer success");
    }

    public static Optional<Table> getTable(String databaseName, String tableName) {
        databaseName = PROCESSOR_CONTROLLER.getDataBaseName(databaseName);
        return BUFFER.get(databaseName).stream().filter(table -> table.getName().equals(tableName)).findFirst();
    }

    public static Column getColumn(String databaseName, String tableName, String columnName) {
        return getTable(databaseName, tableName).get().getColumns()
                .stream().filter(column -> column.getName().equals(columnName)).findFirst().get();
    }

    public static void addTable(Table table) {
        List<Table> databaseTables = BUFFER.getOrDefault(table.getTableSchema(), new ArrayList<>());
        databaseTables.add(table);
        BUFFER.put(table.getTableSchema(), databaseTables);
    }
}
